using Microsoft.Extensions.Logging;
using KnowledgeQA.Core.Interfaces;
using KnowledgeQA.Models.Entities;
using System.Text;
using KnowledgeQA.Core.Utils;

namespace KnowledgeQA.Core.Implementations
{
    /// <summary>
    /// 文本文档处理器
    /// </summary>
    public class TextDocumentProcessor : IDocumentProcessor
    {
        private readonly ILogger<TextDocumentProcessor> _logger;

        public TextDocumentProcessor(ILogger<TextDocumentProcessor> logger)
        {
            _logger = logger;
        }

        public IEnumerable<string> SupportedFileTypes => new[] { ".txt", ".md", ".csv" };

        public bool CanProcess(string fileType)
        {
            return SupportedFileTypes.Contains(fileType.ToLower());
        }

        public async Task<DocumentProcessResult> ProcessAsync(string filePath, Document document)
        {
            var stopwatch = System.Diagnostics.Stopwatch.StartNew();
            var result = new DocumentProcessResult();

            try
            {
                _logger.LogInformation("开始处理文本文档: {FilePath}", filePath);

                // 使用EncodingUtils检测编码并读取文件
                var encoding = await EncodingUtils.DetectFileEncodingAsync(filePath);
                _logger.LogInformation("检测到文件编码: {Encoding}", encoding.EncodingName);

                // 读取文件内容
                var rawContent = await File.ReadAllTextAsync(filePath, encoding);
                _logger.LogInformation("原始内容长度: {RawLength}", rawContent.Length);

                // 使用EncodingUtils清理和验证内容
                var content = EncodingUtils.CleanTextContent(rawContent);
                _logger.LogInformation("清理后内容长度: {CleanedLength}", content.Length);

                // 获取内容统计信息
                var stats = EncodingUtils.GetTextContentStats(content);
                _logger.LogInformation("内容统计 - 总长度: {TotalLength}, 有效字符: {ValidChars}, 无效字符: {InvalidChars}, 中文字符: {ChineseChars}, 无效比例: {InvalidRatio:F2}%", 
                    stats.TotalLength, stats.ValidCharCount, stats.InvalidCharCount, stats.ChineseCharCount, stats.InvalidRatio * 100);

                // 验证内容有效性
                if (!EncodingUtils.IsValidTextContent(content))
                {
                    throw new InvalidOperationException($"文档内容无效 - 无效比例: {stats.InvalidRatio:F2}%, 有效字符数: {stats.ValidCharCount}");
                }

                // 记录内容预览（只显示前200个字符）
                var preview = content.Length > 200 ? content.Substring(0, 200) + "..." : content;
                _logger.LogInformation("文档内容预览: {Preview}", preview);

                result.Content = content;

                // 分块处理
                result.Chunks = await SplitContentAsync(content, document.Id);

                result.Success = true;
                result.ProcessingTime = stopwatch.ElapsedMilliseconds;

                _logger.LogInformation("文本文档处理完成: {FilePath}, 块数: {ChunkCount}, 处理时间: {ProcessingTime}ms", 
                    filePath, result.Chunks.Count, result.ProcessingTime);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "处理文本文档失败: {FilePath}", filePath);
                result.Success = false;
                result.ErrorMessage = ex.Message;
            }
            finally
            {
                stopwatch.Stop();
                result.ProcessingTime = stopwatch.ElapsedMilliseconds;
            }

            return result;
        }

        private async Task<List<DocumentChunk>> SplitContentAsync(string content, int documentId)
        {
            var chunks = new List<DocumentChunk>();
            
            if (string.IsNullOrEmpty(content))
            {
                _logger.LogWarning("文档内容为空，无法分块");
                return chunks;
            }

            var lines = content.Split('\n', StringSplitOptions.RemoveEmptyEntries);
            var chunkSize = 1000; // 每个块大约1000字符
            var currentChunk = new List<string>();
            var currentSize = 0;
            var chunkIndex = 0;

            _logger.LogInformation("开始分块处理，总行数: {LineCount}", lines.Length);

            foreach (var line in lines)
            {
                // 跳过空行或只包含空白字符的行
                if (string.IsNullOrWhiteSpace(line))
                    continue;

                if (currentSize + line.Length > chunkSize && currentChunk.Count > 0)
                {
                    // 创建当前块
                    var chunkContent = string.Join("\n", currentChunk);
                    
                    // 验证块内容
                    if (!string.IsNullOrWhiteSpace(chunkContent))
                    {
                        var chunkStats = EncodingUtils.GetTextContentStats(chunkContent);
                        if (chunkStats.IsValid)
                        {
                            chunks.Add(new DocumentChunk
                            {
                                DocumentId = documentId,
                                Content = chunkContent,
                                ChunkIndex = chunkIndex++,
                                ChunkSize = chunkContent.Length,
                                Status = "Pending"
                            });

                            _logger.LogDebug("创建文档块 {ChunkIndex}, 长度: {ChunkLength}, 有效字符: {ValidChars}", 
                                chunkIndex - 1, chunkContent.Length, chunkStats.ValidCharCount);
                        }
                        else
                        {
                            _logger.LogWarning("跳过无效的文档块，无效比例: {InvalidRatio:F2}%", chunkStats.InvalidRatio);
                        }
                    }

                    // 重置当前块
                    currentChunk.Clear();
                    currentSize = 0;
                }

                currentChunk.Add(line);
                currentSize += line.Length;
            }

            // 添加最后一个块
            if (currentChunk.Count > 0)
            {
                var chunkContent = string.Join("\n", currentChunk);
                if (!string.IsNullOrWhiteSpace(chunkContent))
                {
                    var chunkStats = EncodingUtils.GetTextContentStats(chunkContent);
                    if (chunkStats.IsValid)
                    {
                        chunks.Add(new DocumentChunk
                        {
                            DocumentId = documentId,
                            Content = chunkContent,
                            ChunkIndex = chunkIndex,
                            ChunkSize = chunkContent.Length,
                            Status = "Pending"
                        });

                        _logger.LogDebug("创建最后一个文档块 {ChunkIndex}, 长度: {ChunkLength}, 有效字符: {ValidChars}", 
                            chunkIndex, chunkContent.Length, chunkStats.ValidCharCount);
                    }
                    else
                    {
                        _logger.LogWarning("跳过最后一个无效文档块，无效比例: {InvalidRatio:F2}%", chunkStats.InvalidRatio);
                    }
                }
            }

            _logger.LogInformation("文档分块完成，总块数: {ChunkCount}", chunks.Count);
            return chunks;
        }
    }
} 